
/*
*Pool Public Licence version 0.1 or later
*Released on 20th April 2008.
*Any voilations can be repoted at paritosh@wikiocean.net
*What is treated as voilations can be found at www.wikiocean.net/ppl1-voilations* 
******************************************************************************
* The contents of this file are subject Affero GPL v3 and later with additional conditions.
* The additional conditions are to be considered as part of the Affero GPL v3 and later.
* The additional conditions will supersede the Affero GPLv3 and later in case of conflict.
* ("License"); You may not use this file except in compliance with the License
* You may obtain a copy of the License at http://www.gnu.org/licenses/agpl.html
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License for
* the specific language governing rights and limitations under the License.
* The Initial Developer of the Original Code is Paritosh Pungaliya.
* created by Paritosh Pungaliya are Copyright (C) Paritosh Pungaliya; All Rights Reserved.
* Contributions are Copyright (C) 2001-2008 Paritosh Pungaliya.

* Objective of the additional terms (license) 
* 1) Is to extend the software freedom to freedom to work.
* 2) To ensure that knowledge is free from monopoly of agencie(s).
* 3) To avoid a situation where big corporates or investors can buy out free software groups and companies and then start milking the communities built around it.
* (this trend can be seen how the openness changes in companies that get Venture Capital funding.)
* (if you agree to this logic I invite you to our group to work together)

* Additional conditions
*  0) Source code will also include
* 	a) data dictionaries, data ontologies which are used to alter the behavior of code or to control           the features of application.
* 	b) Any code generated or derived automatically or manually from this code or logic
*  1) The revenue generated by deploying, implementing , selling services and other activities
*  	 based on this source code should be shared 100%, between the people working on it.
*  2) Capital invested should be given only fixed rate of return or linked to revenue/surplus growth for limited time.
*  3) People working on the project should always have an option to replace the capital provider in full or part with lower cost capital.
*  4) Their should not be any ownership which can be sold as a claim on future profit to be generated from the work of people working on the code.
*  5) Brand thus generated should belong to the group.
*  6) For old and new members revenue sharing should be equal for same work equivalent.
*  7) The share of revenue should be decided by bidding for work before allocation of work within the group.
*  8) Before bidding various method of measuring the work should be clearly defined and published in public domain. Any change in process should also be publised in public domain imediately.
*  9) All data related to to revenue sharing should be published as and when generated in public domain.
*  10) For group of people having size more than 10 people will have to make it open online for others to participate in bids. 
*  11) All people involved in related and sub project will be treated as a group.
*  12) Once this license is being used for a certain code then all and any other software services being provided by the group should complusorilly come under 100% revenue sharing.
*  13) Cross subsidization should not happen under this revenue share, no additional benefit should be drawn from the people, by the employing agency.
*  14) Any position or knowledge or legal structure created relating to people working on code, which adversely affects the spirit of 100% revenue share will be treated as a violation.
*  15) Revenue sharing defined.
*     a) includes direct revenue and also intangible gains like brand, and organization.
*     b) No personal judgment should be involved in judging the distribution of revenue.It has to be pre-defined formula based.
*     c)100% of revenue should be shared before expenses and recievers should have control over what expenses to incur.
*     d)For the work done in any month by contributing group member, working on any project can be given revenue share from the work done by the group, for a maximum of 18 months after that month.
*     e)Revenue should be apportioned to the month in which work is done and not when received.
*  The group fulfilling the above conditions also has to be a wiki ecosystem further defined in www.wekosystem.org or read about Wekosystem at www.wikiocean.net

*  ******************************************************************************
*/  
package pool.preprocess;


import java.util.Enumeration;
import java.util.Hashtable;
import java.util.Vector;

import pool.tablename.Property_details;
import pool.tablename.Pool;

//import file.SearchRecord;
import timer.ExecutionTimer;
import timer.TimerRecordFile;
import utility.CapitalChar;
import utility.ConvertToLower;
import utility.Input;
import database.RecordSearch;
import dbmanager.Column;
import dbmanager.DBManager;
import dbmanager.GetIdName;


public class Validation  implements Process
{
	Object obj;
	DBManager database;
	Pool masterclass;
	String TYPE="type";
	GetIdName gid;
	String mastername;
	String MASTERNAME="mastername";
	String type;
	String VALIDATION="validation";
	String validation;
	String ISMANDARORY = "ismandatory";
	StringBuffer Error = new StringBuffer();
	public Hashtable<Object, Object> ErrorMap = new Hashtable<Object, Object>();
	public Hashtable<Object,Object> Errortable =new Hashtable<Object,Object>();
	boolean flagref;
	
	public void setObject(Object masterclass, DBManager database) 
	{
		ExecutionTimer t = new ExecutionTimer();
		 t.start();
		this.masterclass =(Pool)  masterclass;
		this.database = database;
		gid = new GetIdName(database);
		TYPE  = gid.getId(TYPE);
		VALIDATION = gid.getId(VALIDATION);
		ISMANDARORY = gid.getId(ISMANDARORY);
		MASTERNAME = gid.getId(MASTERNAME);
		t.end();
		TimerRecordFile timerFile=new TimerRecordFile("errorvalidation","Validation","setObject",t.duration());
	}
	
	public void setType(String type)
	{
		ExecutionTimer t = new ExecutionTimer();
		 t.start();
		this.type =type;
		t.end();
		TimerRecordFile timerFile=new TimerRecordFile("errorvalidation","Validation","setType",t.duration());
	}
	
	public void process(String validationobject)
	{
	ExecutionTimer t = new ExecutionTimer();
	t.start();
	//String Masterpath = Input.MASTERREPORTSPATH + validationobject + "//" + validationobject + "_mid" + Input.FILRFORMAT;
	/*SearchRecord sr = new SearchRecord(Masterpath);
	sr.fileOpen();*/
	Hashtable<Object,Object> temphashtable = new Hashtable<Object,Object>();
	Hashtable<Object,Object> temptable = new Hashtable<Object,Object>();
	temphashtable.clear();
	temphashtable.put("mid", validationobject);
	/*String line[] = sr.getRecordSet(temphashtable);
	sr.fileClose();*/
	temphashtable.put("td", "null");
	RecordSearch ps = new RecordSearch(database);
	ps.setConditionMap(temphashtable);
	String line[] = ps.getArrayFromResultSet();	
	Hashtable<Object, Object> masterhashtabel = ConvertToLower.convertHashKey(masterclass.getHashtabel());
	Hashtable<Object, Object> Basichashtabel =ConvertToLower.convertHashKey(masterclass.getBasicHashtable());
	Vector<Object>PropertyVector = masterclass.getpropertyVector();
	System.out.println("Hash Table is"+masterhashtabel);
	System.out.println("Hash Table is"+PropertyVector);
	boolean typeflag=false;
	Vector<Object> defaultproperty =new Vector<Object>();
	try 
	{
		for(int i=0;i<PropertyVector.size();i++)
		{
			if(!typeflag)
			{
				Property_details pd = (Property_details)PropertyVector.get(i);
				temptable.clear();
				temptable.putAll((Hashtable<Object, Object>)  ConvertToLower.convertHashKey(pd.PropertyMap));
				if(temptable.containsKey("pid"))
				{
					String value=temptable.get("pid").toString();
					if(value.equals(TYPE))
					{
						typeflag =true;
						break;
					}	
				}
			}
		}
	}
	catch (Exception e) 
	{
		e.printStackTrace();
	}
	
	
	for(int i=0;i<line.length;i++)
	{
			boolean flag=false;
			String splitline[] = line[i].split("\t");
			System.out.println("Validation object is"+splitline[Column.pid_index]);
			String property =gid.getItem(splitline[Column.pid_index-1]).toLowerCase();
			defaultproperty.add(splitline[Column.pid_index-1]);
			if(MASTERNAME.equals((splitline[Column.pid_index-1])))
			{
				//String path = Input.MASTERREPORTSPATH + splitline[Column.pv_index-1] + "//" + splitline[Column.pv_index-1] + "_mid" + Input.FILRFORMAT;
				String actualvalue = masterhashtabel.get("name").toString();
				//sr = new SearchRecord(path);
				temphashtable.clear();
				temphashtable.put("mid", splitline[Column.pv_index-1]);
				/*sr.fileOpen();
				String result[] = sr.getRecordSet(temphashtable);
				sr.fileClose();*/
				temphashtable.put("td", "null");
				ps = new RecordSearch(database);
				ps.setConditionMap(temphashtable);
				String result[] = ps.getArrayFromResultSet();
				loadvalidationobject(result, actualvalue, splitline[Column.pid_index-1],"");
				flag = true;
			}
			 if(masterhashtabel.containsKey(property))
			{
			//	String path = Input.MASTERREPORTSPATH + splitline[Column.pv_index-1] + "//" + splitline[Column.pv_index-1] + "_mid" + Input.FILRFORMAT;
				String actualvalue =masterhashtabel.get(property).toString();
				String basicvalue = Basichashtabel.get(property).toString();
				/*sr.fileOpen();
				sr = new SearchRecord(path);*/
				temphashtable.clear();
				temphashtable.put("mid", splitline[Column.pv_index-1]);
				/*String result[] = sr.getRecordSet(temphashtable);
				sr.fileClose();*/
				temphashtable.put("td", "null");
				ps = new RecordSearch(database);
				ps.setConditionMap(temphashtable);
				String result[] = ps.getArrayFromResultSet();
				/*if(splitline[Column.pid_index-1].equalsIgnoreCase("pid"))
				try 
				{
					if(actualvalue.equals("0"))
						actualvalue = temptable.get("vt").toString();
					else
						actualvalue = gid.getItem(actualvalue);
				}
				catch (Exception e1) 
				{
					e1.printStackTrace();
				}*/
				loadvalidationobject(result, actualvalue, splitline[Column.pid_index-1],basicvalue);
				try 
				{
					if(splitline[Column.ref_index-1].equals("0")==true||splitline[Column.ref_index-1].equals("no$")==true);
					else
					{
						//String refpath = Input.MASTERREPORTSPATH + splitline[Column.pv_index-1] + "//" + splitline[Column.ref_index-1] + "_mid" + Input.FILRFORMAT;
						String refactualvalue = masterhashtabel.get(splitline[Column.ref_index-1]).toString();
						//sr = new SearchRecord(refpath);
						temphashtable.clear();
						temphashtable.put("mid", splitline[Column.ref_index-1]);
						//String refresult[] = sr.getRecordSet(temphashtable);
						temphashtable.put("td", "null");
						ps.setConditionMap(temphashtable);
						String refresult[] = ps.getArrayFromResultSet();
						if(refactualvalue.equals("0"))
							refactualvalue = temptable.get("vt").toString();
						else
							refactualvalue = gid.getItem(actualvalue);
						flagref = true;
						loadvalidationobject(refresult, refactualvalue, splitline[Column.ref_index-1],"");
					}
				}
				catch (Exception e) 
				{
					e.printStackTrace();
				}
				flag = true;
			}
			try 
			{
				for(int j=0;j<PropertyVector.size();j++)
				{
					Property_details pd = (Property_details)PropertyVector.get(j);
					temptable.clear();
					temptable.putAll((Hashtable<Object, Object>)  ConvertToLower.convertHashKey(pd.PropertyMap));
					System.out.println("Hash Table is "+temptable);
					if(temptable.get("pid").equals((splitline[Column.pid_index-1])))
					{
						String path = Input.MASTERREPORTSPATH + splitline[Column.pv_index-1] + "//" + splitline[Column.pv_index-1] + "_mid" + Input.FILRFORMAT;
						String actualvalue = temptable.get("pv").toString();
						if(actualvalue.equals("0"))
							actualvalue = temptable.get("vt").toString();
						else
							actualvalue = gid.getItem(actualvalue);
						//sr = new SearchRecord(path);
						temphashtable.clear();
						temphashtable.put("mid", splitline[Column.pv_index-1]);
						//String result[] = sr.getRecordSet(temphashtable);
						temphashtable.put("td", "null");
						ps = new RecordSearch(database);
						ps.setConditionMap(temphashtable);
						String result[] = ps.getArrayFromResultSet();
						loadvalidationobject(result, actualvalue, splitline[Column.pid_index-1],"");
						if(splitline[Column.ref_index-1].equals("0")==true||splitline[Column.ref_index-1].equals("no$")==true);
						else
						{
							String refpath = Input.MASTERREPORTSPATH + splitline[Column.ref_index-1] + "//" + splitline[Column.ref_index-1] + "_mid" + Input.FILRFORMAT;
							//sr = new SearchRecord(refpath);
							Hashtable<Object, Object > newhashtable = new  Hashtable<Object, Object>();
							newhashtable.put("mid", splitline[Column.ref_index-1]);
							//String refresult[] = sr.getRecordSet(newhashtable);
							temphashtable.put("td", "null");
							ps = new RecordSearch(database);
							ps.setConditionMap(newhashtable);
							String refresult[] = ps.getArrayFromResultSet();
							String refactualvalue = temptable.get("ref").toString();
							refactualvalue = gid.getItem(refactualvalue);
							flagref = true;
							loadvalidationobject(refresult, refactualvalue, splitline[Column.pid_index-1],"");
							flagref =false;
						}
						flag = true;
					}
				}
			}
			catch (Exception e) 
			{
				e.printStackTrace();
			}			
			if(flag==false && typeflag == true)
			{
				flag = true;
				String actualvalue = temptable.get("pv").toString();
				if(actualvalue.equals("0"))
					actualvalue = temptable.get("vt").toString();
				else
					actualvalue = gid.getItem(actualvalue);	
				//sr = new SearchRecord(path);
				temphashtable.clear();
				temphashtable.put("mid", splitline[Column.pv_index-1]);
				temphashtable.put("pid", ISMANDARORY);
				temphashtable.put("td", "null");
				//String result[] = sr.getRecordSet(temphashtable);
				
				ps = new RecordSearch(database);
				ps.setConditionMap(temphashtable);
				String result[] = ps.getArrayFromResultSet();
				loadvalidationobject(result , actualvalue, splitline[Column.pid_index-1],"");
				try 
				{
					if(!splitline[Column.ref_index-1].equals("0"))
					{
						String refpath = Input.MASTERREPORTSPATH + splitline[Column.ref_index-1] + "//" + splitline[Column.ref_index-1] + "_mid" + Input.FILRFORMAT;
						String refactualvalue ="";
						try 
						{
							refactualvalue = temptable.get("ref").toString();
						}
						catch (Exception e) 
						{
						}
						//sr = new SearchRecord(refpath);
						temphashtable.clear();
						temphashtable.put("mid", splitline[Column.ref_index-1]);
						//String refresult[] = sr.getRecordSet(temphashtable);
						temphashtable.put("td", "null");
						ps = new RecordSearch(database);
						ps.setConditionMap(temphashtable);
						String refresult[] = ps.getArrayFromResultSet();
						//refactualvalue = gid.getItem(actualvalue);
						refactualvalue = actualvalue;					
						loadvalidationobject(refresult, refactualvalue, splitline[Column.pv_index-1],"");
					}
				}
				catch (Exception e) 
				{
					e.printStackTrace();
				}
			}	
		}
	try 
	{
		for(int i=0;i<PropertyVector.size();i++)
		{
			Property_details pd = (Property_details)PropertyVector.get(i);
			temptable.clear();
			temptable.putAll((Hashtable<Object, Object>)  ConvertToLower.convertHashKey(pd.PropertyMap));
			if(!defaultproperty.contains(temptable.get("pid")))
			{
				Error.append(gid.getItem(temptable.get("pid").toString())+" is not valid property,");
			}
		}
	}
	catch (Exception e) 
	{
		e.printStackTrace();
	}
	Enumeration<Object> masterenum = masterhashtabel.keys();
	/*while(masterenum.hasMoreElements())
	{
		String key = masterenum.nextElement().toString();
		String Masterkey = gid.getId(key);
		if(Masterkey.equals("no$") || Masterkey.equals("0"))
			Masterkey = key;
		if(!defaultproperty.contains(Masterkey))
		{
			key = gid.getId(Masterkey);
			if(key.equals("no$") || key.equals("0"))
				key = Masterkey;
			Error.append(key+" is not valid property,");
		}
	}*/
	if(Error.length()!=0)
		{
			ErrorMap.put("Errorvalidation",Error);
			Errortable.clear();
			Errortable.put("ErrorInput",ErrorMap);
		}
	t.end();
	TimerRecordFile timerFile=new TimerRecordFile("errorvalidation","Validation","process",t.duration());
	}
	public Object getObject() 
	{
			return this;
	}
	
	@SuppressWarnings("unchecked")
	public void loadvalidationobject(String [] line,String actualvalue,String pvvalue,String basicvalue)
	{	
		ExecutionTimer t = new ExecutionTimer();
		 t.start();
		for(int k=0;k<line.length;k++)
		{	
		String Splitline[]=line[k].split("\t");
		String validationobj = Splitline[Column.pid_index-1];
		String validationvalue = Splitline[Column.pv_index-1];
	     if(validationvalue.equals("0"))
	    	 validationvalue = Splitline[Column.vt_index-1];
	     else
	    	 validationvalue = gid.getItem(validationvalue);
	     String Refvalue;
		try
		{
			Refvalue = Splitline[Column.ref_index-1];
		}
		catch (Exception e1) 
		{
			Refvalue = "";
		}
	     validation.Validation errorvalidation;
	     try 
	     {
    	    Class C = Class.forName("validation."+CapitalChar.makeFirstCharCapital(gid.getItem(validationobj)));
			errorvalidation = (validation.Validation )C.newInstance();
			errorvalidation.setDbmanager(database);
			errorvalidation.setBasicvalue(basicvalue);
			if(!errorvalidation.validate(actualvalue,validationvalue,Refvalue))
			{
				String MasterName = gid.getItem(pvvalue);
				if(flagref)
				Error.append("ref value of "+MasterName+" " +errorvalidation.getMessage() + ", ");
				else
				Error.append(MasterName+" " +errorvalidation.getMessage() + ", ");
				
			}
		 } 
	     catch (ClassNotFoundException e) 
	     {
		 }
	     catch (InstantiationException e) 
	     {
			e.printStackTrace();
		 } 
	     catch (Exception e) 
	     {
			e.printStackTrace();
		}
	     
	}
		t.end();
		TimerRecordFile timerFile=new TimerRecordFile("errorvalidation","Validation","loadvalidationobject",t.duration());
  }
	public Hashtable<Object, Object> gethashtable() 
	{	
		return Errortable;
	}

	public void setType(String type, String table) 
	{
		ExecutionTimer t = new ExecutionTimer();
		 t.start();
		this.type =type;
		t.end();
		TimerRecordFile timerFile=new TimerRecordFile("combinereport.query","Report_master","setType",t.duration());
	}		
}
	
	
		
	
	
	
	